#pragma once
#include <QObject>
#include <QJsonValue>
#include <QJsonObject>
#include <QJsonArray>
#include <QFile>
#include <QTcpSocket>
#include <QMutex>
#include "FileTransferDef.h"

class FileReceiver : public QObject
{
	Q_OBJECT
protected:
	FileReceiver(qintptr socketDescriptor, const QList<FileTransferDef::sRevSavePath>& revSavePaths);
	~FileReceiver();

public:
	QString getId() const;
	QString getIp() const;

signals:
	void signalClose();
	void signalReceiveProgressChanged(int percentage);
	void signalFileReceiveFinished(const QString& filePath, const QByteArray& userData);
	void signalReceiveStart();
	void signalReceiveError(FileTransferDef::eRecevieError);

protected slots:
	void onMessageReceived();
	void onSocketDisconnected();

private:
	void reply(FileTransferDef::eRevFileCmd cmd, const QJsonObject& param);

private:
	QString mId;
	QTcpSocket* mSocket;
	QString mIp;
	QList<FileTransferDef::sRevSavePath> mSavePaths;
	QFile *mFile = nullptr;

	QString mRelativeFilePath;
	QString mFilePath;
	QString mTempFilePath;
	QByteArray mUserData;
	qint64 mFileSize = 0;
	QString mSendId;
	qint64 mReceivedSize = 0;
	int mPercentage = 0;

	friend class HiFileReceiverManager;
};

class HiFileReceiverManager : public QObject
{
protected:
	HiFileReceiverManager();
	~HiFileReceiverManager();

public:
	static HiFileReceiverManager* getInstance();

public:
	FileReceiver* createReceiver(qintptr socketDescriptor, const QList<FileTransferDef::sRevSavePath>& revSavePaths);
	void destroyReceiver(FileReceiver*);
	QMap<QString, FileReceiver*> getAllReceivers();
	QMap<QString, FileReceiver*>::const_iterator getAllReceiversBeginIterator();

private:
	QMap<QString, FileReceiver*> mIdAndReceiverMap;
	QMap<FileReceiver*, QThread*> mReceiverAndThreadMap;
	static QMutex mLock;
	static HiFileReceiverManager* mInstance;
};
HiFileReceiverManager* getFileReceiverManager();